Skip to content

feat(toolchain): outdated warnings for toolchain + agent skills, install skills from repo head - #3970

Merged
ATX24 merged 11 commits into
canaryfrom
dhilan/update-mechanism
Jul 10, 2026
Merged

ATX24 merged 11 commits into
canaryfrom
dhilan/update-mechanism

Conversation

@ATX24

@ATX24 ATX24 commented Jul 10, 2026 •

Copy link
Copy Markdown
Contributor

Skill & toolchain freshness: outdated warnings, repo-head skill installs, and provenance tracking

Previously the toolchain never told users they were behind (no check, no nudge — state.toml stayed frozen until a manual baml toolchain update), and baml agent install installed the skill snapshot attached to the running toolchain version rather than the latest skills. This PR makes staleness visible for both, and makes skill installs track the skill repo head.

What changed

1. baml agent install installs the head of BoundaryML/baml-skill

  • The default (no flags) now resolves the current main commit SHA via the GitHub API, then downloads the tarball pinned to that exact commit — so what gets recorded always matches what got installed.
  • --latest is removed — it's the standard behavior now. --from <url|archive|dir> remains for custom sources.
  • The old toolchain-release snapshot path (checksummed baml-agent-skills-{version}.tar.gz) is removed entirely: the build-agent-skills release job, the scripts/package-agent-skills packaging script, and the BAML_AGENT_SKILLS_RELEASE_VERSION env escape hatch are all gone. Skills are no longer versioned with or attached to toolchain releases.
  • After a successful install, provenance is recorded in ~/.baml/state.toml, mirroring how channel versions are recorded:
[skills]
installed_commit = "53cbd45c2b3002c9b40e25eadd68b01840d2dee3"
installed_at = "2026-07-10T18:47:20Z"
  • The [skills] section lives in a new shared baml_release::skills module used by both the wrapper and baml-cli; both writers use clobber-safe writes so neither can drop the other's sections.

2. The wrapper warns when you're outdated (or have no skills at all)

On every normal command (baml generate, baml run, …), before exec'ing baml-cli, the wrapper compares local state against the freshness caches and prints to stderr (bold-yellow warning: prefix, TTY-aware, matching existing CLI diagnostics):

warning: Your version of baml for toolchain: canary is outdated. Update it with baml toolchain update.
warning: Your baml skill is outdated, use baml agent install to upgrade it.
warning: No baml skill is installed, set it up with baml agent install.
  • Toolchain: fires when the cached channel manifest records a newer version than the active one. Pinned exact versions never warn (they don't advance, by design).
  • Skill (missing): projects with no baml-* skills installed get the install prompt on every command, regardless of caches — so users discover skills exist.
  • Skill (outdated): projects with skills warn when [skills].installed_commit is missing or differs from the cached latest skill-repo commit. The project-skills check is the primary gate: global provenance never triggers upgrade warnings in a project that has no skills (it gets the install prompt instead).

3. Auto-refresh at a 24h cadence, hidden behind the command

  • Caches (channel manifest + latest skill commit) refresh over the network at most once per 24h window, piggybacked on the first command of the day: shared 5s budget, silent on failure, and a .last-check marker throttles retries so an offline machine pays the cost once per day, not per command.
  • The refresh is lazy: it runs on a background thread while baml-cli executes, not before it. Warnings from existing caches still print immediately (pure local reads). After the command exits, the wrapper waits out whatever remains of the 5s budget (a command that ran 3s waits at most 2s more) and prints only warnings the fresh caches newly justify — a warning already shown up front is never duplicated.
  • Implementation nuance: on the rare refresh-due invocation the wrapper spawns baml-cli and waits (exec would kill the refresh thread); every other invocation keeps the zero-overhead Unix exec fast path.
  • This activates the previously dead [update] auto_check config flag: default on, opt out with auto_check = false in ~/.baml/config.toml (opting out disables the network refresh; warnings still compare against whatever explicit commands cached).
  • Warnings themselves print on every command while you're behind; only the checking is throttled.

4. Toolchain commands report skill status

  • baml toolchain status gains a skill section (skill installed: / skill latest: / skill status: with an upgrade hint); network failure degrades to (failed to check) rather than failing the command.
  • baml toolchain use / update do a best-effort skill freshness check afterward.

Expected behavior summary

Scenario Behavior
Tracked channel behind cached manifest warning: on stderr on every command until toolchain update
Project has no baml-* skills install prompt on every command until agent install runs
Skills present, provenance behind repo head upgrade warning until agent install re-runs
Skills present, no provenance recorded upgrade warning (installs predating provenance tracking)
Skills present, provenance matches, or no cache yet silence
Caches fresh (<24h) zero network on normal commands; wrapper execs straight into baml-cli
Refresh due (first command of the day) refresh runs in the background during the command; newly discovered warnings print after it exits
Network down one refresh attempt per 24h costing at most the unused part of the 5s budget after the command, otherwise silent
auto_check = false no wrapper-initiated network, passive comparisons only
agent install succeeds provenance + cache updated; warnings clear immediately

New env overrides (for mirrors/tests; never required)

BAML_AGENT_SKILLS_REPO, BAML_AGENT_SKILLS_COMMITS_URL, BAML_AGENT_SKILLS_ARCHIVE_BASE_URL — all default to BoundaryML/baml-skill on GitHub.

Breaking / behavioral notes

  • baml agent install --latest no longer exists (its behavior is the default).
  • Installs are no longer checksum-verified against a release asset (content is pinned by commit SHA instead). The per-version release asset and its BAML_AGENT_SKILLS_RELEASE_VERSION escape hatch are removed; existing release assets on old tags are unaffected but new releases won't ship one.
  • Toolchain releases no longer build/publish baml-agent-skills-{version}.tar.gz (the build-agent-skills job and packaging script are deleted from release-baml-language.yml).
  • The wrapper now performs opportunistic network requests (default-on auto_check).
  • Projects without skills now see an install prompt on every command.

Testing

  • Unit tests across the three crates: cache TTL + marker throttling, outdated/missing-skill decision logic, state round-trips that prove [channels.*]/[skills] can't clobber each other (including refusing to overwrite a corrupt state.toml), [skills] clearing for custom-source installs, auto_check semantics, archive/URL handling.
  • 10 wrapper e2e tests running the real baml binary against a temp BAML_HOME, asserting warnings on stderr (install prompt vs upgrade warning, empty skill dirs don't count as installed), marker throttling with a dead endpoint, opt-out behavior, and the lazy-refresh path (background refresh persists the cache and surfaces the warning after the command, exactly once).
  • 1 agent install e2e test running the real baml-cli against a stubbed local GitHub server, asserting installed skills + recorded provenance + cache update.
  • Manually verified against live GitHub/canary: real install recorded head commit, toolchain status showed both sections, warning cleared after install; agent --help / agent install --help verified to no longer mention --latest.
  • cargo clippy --all-targets -- -D warnings passes locally for all three touched crates (the initial CI run flagged strict cast lints in the date helper plus two pedantic lints; fixed in the final commit with try_from + in-range fallbacks instead of as casts).
  • Branch is up to date with the latest canary (merged in).

Summary by CodeRabbit

  • New Features

    • Added automatic freshness checks for installed toolchains and agent skills.
    • Added warnings when updates are available, with throttled background checks and an opt-out setting.
    • agent install now installs skills from the latest repository commit or a specified URL/path.
    • Skill installations now record commit provenance and support status reporting.
  • Bug Fixes

    • Preserved unrelated configuration sections when updating saved state.
    • Improved handling of missing or invalid freshness caches.
  • Chores

    • Removed agent-skill packaging from the release pipeline.

ATX24 and others added 3 commits July 10, 2026 12:30
…helpers

New baml_release::skills module shared by the wrapper and baml-cli: skill
repo URL builders (env-overridable for mirrors/tests), [skills] provenance
state in state.toml written via read-modify-write so it never clobbers the
wrapper-owned [channels.*] sections, a latest-commit freshness cache, and a
GitHub API fetch for the skill repo head commit.

Co-authored-by: Cursor <[email protected]>
…rovenance

baml agent install now defaults to the current head of BoundaryML/baml-skill:
it resolves the main commit SHA first, downloads the tarball pinned to that
exact commit, and records [skills] provenance in state.toml (plus the
freshness cache) after a successful install. The --latest flag is removed
since it is the standard behavior; --from remains for custom sources and the
toolchain-release snapshot survives only behind
BAML_AGENT_SKILLS_RELEASE_VERSION. Includes an e2e test that runs the real
binary against a stubbed GitHub server and asserts the recorded provenance.

Co-authored-by: Cursor <[email protected]>
…ated

The wrapper now surfaces staleness on normal commands: before exec'ing
baml-cli it compares the recorded channel version against the cached channel
manifest and the [skills] provenance against the cached latest skill commit,
printing a styled bold-yellow warning: line on stderr when either is behind.

Caches auto-refresh over the network at most once per 24h window (5s timeout,
silent on failure, throttled by a .last-check marker so offline machines do
not retry every command), activating the previously dead [update] auto_check
config flag with default-on/opt-out semantics. toolchain status gains a skill
section and toolchain use/update do a best-effort skill check afterward. The
wrapper's State struct now round-trips foreign state.toml sections so it
cannot drop the CLI-written [skills] entry. Covered by unit tests plus an
e2e suite that runs the real wrapper binary against a temp BAML_HOME.

Co-authored-by: Cursor <[email protected]>
@vercel

vercel Bot commented Jul 10, 2026 •

Copy link
Copy Markdown

The latest updates on your projects. Learn more about Vercel for GitHub.

Project Deployment Actions Updated (UTC)
beps Ready Ready Preview, Comment Jul 10, 2026 10:39pm
promptfiddle Ready Ready Preview, Comment Jul 10, 2026 10:39pm
promptfiddle2 Ready Ready Preview, Comment Jul 10, 2026 10:39pm

Request Review

@coderabbitai

coderabbitai Bot commented Jul 10, 2026 •

Copy link
Copy Markdown
Contributor

Review Change Stack

📝 Walkthrough

Walkthrough

The PR adds shared skill provenance and commit-cache APIs, changes skill installation to use exact repository commits, adds wrapper freshness checks and warnings with throttled refreshes, and removes packaged agent-skill release artifacts.

Changes

Skills freshness lifecycle

Layer / File(s) Summary
Shared skill state and commit APIs
baml_language/crates/baml_release/...
The release crate adds skill repository configuration, commit fetching, provenance persistence, cached commit storage, timestamp generation, and tests.
Commit-based skill installation
baml_language/crates/baml_cli/src/agent_command.rs, baml_language/crates/baml_cli/tests/agent_install_e2e.rs
agent install supports URL, directory, and latest-commit sources, records provenance for repository installs, and validates the flow through a local HTTP server.
Wrapper freshness checks and warnings
baml_language/crates/baml/...
The wrapper adds passive manifest and skill refreshes, throttling, auto-check configuration, freshness warnings, status output, timeout-aware HTTP clients, and unit/E2E tests.
Release pipeline packaging removal
.github/workflows/release-baml-language.yml
The release workflow no longer builds or publishes agent-skill archives.

Estimated code review effort: 4 (Complex) | ~60 minutes

Sequence Diagram(s)

sequenceDiagram
  participant User
  participant BamlWrapper
  participant SkillAPI
  participant SkillCache
  participant BamlCLI
  User->>BamlWrapper: run command
  BamlWrapper->>SkillCache: read cached freshness data
  BamlWrapper->>SkillAPI: refresh stale skill commit
  SkillAPI-->>SkillCache: store latest commit
  BamlWrapper->>User: emit local freshness warning
  BamlWrapper->>BamlCLI: forward command
Loading

Possibly related PRs

Poem

A rabbit checks the cache at dawn,
Finds fresh commits and hops along.
Skills install with provenance bright,
Warnings guide the wrapper right.
Release bundles vanish from sight.

🚥 Pre-merge checks | ✅ 5
✅ Passed checks (5 passed)
Check name Status Explanation
Docstring Coverage ✅ Passed Docstring coverage is 100.00% which is sufficient. The required threshold is 80.00%.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title clearly summarizes the main changes: freshness warnings and installing skills from repo head.
✨ Finishing Touches
📝 Generate docstrings
  • Create stacked PR
  • Commit on current branch
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch dhilan/update-mechanism

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands.

@github-actions

Copy link
Copy Markdown

⏭️ Performance benchmarks were skipped

Perf benchmarks (CodSpeed) are opt-in on pull requests — they no longer run on every push. They always run automatically after merge to canary/main.

To run them on this PR, do any of the following, then push a commit (or re-run CI):

  • Add RUN_CODSPEED=1 to the PR description, or
  • Include run-perf or /perf in the PR title or any commit message.

@vercel
vercel Bot temporarily deployed to Preview – promptfiddle2 July 10, 2026 19:49 Inactive
Projects without any baml-* agent skills now get a warning on every command
(No baml skill is installed, set it up with baml agent install), instead of
staying silent. Projects with skills keep the upgrade warning when provenance
is missing or behind the cached latest commit; the project-skills check is
now the primary gate, so global provenance no longer triggers upgrade
warnings in skill-less projects. Decision logic extracted into a pure
skill_warning_message helper with unit tests, plus updated e2e coverage.

Co-authored-by: Cursor <[email protected]>
@github-actions

github-actions Bot commented Jul 10, 2026 •

Copy link
Copy Markdown

Binary size checks passed

✅ 7 passed

Artifact Platform File Gzip Gated on Baseline Delta Status
✅ baml-cli Linux 🔒 22.1 MB 9.4 MB file 21.5 MB +539.8 KB (+2.5%) OK
✅ packed-program Linux 🔒 15.9 MB 6.7 MB file 15.6 MB +296.3 KB (+1.9%) OK
✅ baml-cli macOS 🔒 17.0 MB 8.2 MB file 16.6 MB +414.8 KB (+2.5%) OK
✅ packed-program macOS 🔒 12.3 MB 5.9 MB file 12.1 MB +232.0 KB (+1.9%) OK
✅ baml-cli Windows 🔒 18.6 MB 8.4 MB file 18.1 MB +451.6 KB (+2.5%) OK
✅ packed-program Windows 🔒 13.3 MB 6.0 MB file 13.0 MB +243.1 KB (+1.9%) OK
✅ bridge_wasm WASM 14.7 MB 🔒 4.2 MB gzip 4.1 MB +120.9 KB (+3.0%) OK

🔒 = the size this artifact is GATED on (ceiling + delta). Binaries gate on file size (installed binary); WASM gates on gzip (download size). The other size is shown for information only.


Generated by cargo size-gate · workflow run

@vercel
vercel Bot temporarily deployed to Preview – beps July 10, 2026 19:55 Inactive
CI runs clippy with -D warnings, which rejected the numeric casts in the
skills date helper (cast_possible_wrap/truncation/sign_loss), a
nonminimal_bool in file_older_than, and format_push_string in the e2e
test. Replace the casts with try_from with in-range fallbacks and
simplify the boolean with is_none_or.

Co-authored-by: Cursor <[email protected]>
@vercel
vercel Bot temporarily deployed to Preview – beps July 10, 2026 20:01 Inactive
@vercel
vercel Bot temporarily deployed to Preview – promptfiddle2 July 10, 2026 20:09 Inactive
@vercel
vercel Bot temporarily deployed to Preview – promptfiddle July 10, 2026 20:12 Inactive
@ATX24
ATX24 marked this pull request as ready for review July 10, 2026 20:13
@vercel
vercel Bot temporarily deployed to Preview – beps July 10, 2026 20:13 Inactive
@vercel
vercel Bot temporarily deployed to Preview – promptfiddle2 July 10, 2026 20:20 Inactive

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 5

🧹 Nitpick comments (1)
baml_language/crates/baml_cli/tests/agent_install_e2e.rs (1)

54-60: 📐 Maintainability & Code Quality | 🔵 Trivial | ⚡ Quick win

Assert that the exact resolved commit is downloaded.

The stub accepts /archive/main or any other ref, so a regression away from commit-pinned installation would still pass.

Proposed test tightening
-            } else if path.starts_with("/archive/") {
+            } else if path == format!("/archive/{COMMIT}") {
                 ("application/gzip", skill_archive())
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@baml_language/crates/baml_cli/tests/agent_install_e2e.rs` around lines 54 -
60, Update the request handling in the agent-install test’s stub server so the
`/archive/` branch asserts that the requested path contains the exact resolved
commit returned by the `/commits` response, rather than accepting any ref such
as `main`. Track or derive the expected commit and fail the test when the
archive URL is not pinned to it.
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@baml_language/crates/baml_cli/src/agent_command.rs`:
- Around line 87-89: The install flow must clear stale installed-commit
provenance when the loaded source has no commit, including --from and
release-snapshot paths. Update the logic surrounding loaded.commit and
record_installed_commit to remove or replace the existing installed_commit entry
whenever commit is None, while retaining normal recording for committed sources;
apply the same behavior across the related install branches.

In `@baml_language/crates/baml_release/src/skills.rs`:
- Around line 63-68: Update state handling around state_path() so skill
provenance is scoped to each project installation root rather than stored as one
global commit. Key provenance by the canonical install root, or place its state
file beside the project, and update the agent install/read/validation paths
consistently while preserving the wrapper-owned toolchain section.
- Around line 104-117: Make write_skills_state lossless and concurrency-safe:
only initialize an empty TOML document when reading state_path returns NotFound,
while propagating other read or parse failures instead of falling back to an
empty table. Add a cross-process lock around the entire read-modify-write
transaction, including parsing, updating the skills entry, serialization, and
atomic rename; apply the same locking and error-handling changes to the related
state update function around lines 167–175.

In `@baml_language/crates/baml/src/main.rs`:
- Around line 569-586: Use a single total timeout budget for the passive refresh
logic surrounding fetch_manifest_with_timeout and fetch_latest_skill_commit,
rather than allowing each serial request its own AUTO_CHECK_TIMEOUT. Establish
one deadline before the refreshes, calculate remaining time before each request,
and skip or bound any refresh when the budget is exhausted.
- Around line 678-685: Update dir_contains_baml_skill to count only valid skill
installations: inspect entries whose names start with “baml-”, verify each is a
directory, and require that it contains a SKILL.md file before returning true.

---

Nitpick comments:
In `@baml_language/crates/baml_cli/tests/agent_install_e2e.rs`:
- Around line 54-60: Update the request handling in the agent-install test’s
stub server so the `/archive/` branch asserts that the requested path contains
the exact resolved commit returned by the `/commits` response, rather than
accepting any ref such as `main`. Track or derive the expected commit and fail
the test when the archive URL is not pinned to it.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Repository UI

Review profile: CHILL

Plan: Pro

Run ID: b1b96241-8924-4c87-854e-5014ab8acd39

📥 Commits

Reviewing files that changed from the base of the PR and between e9d66b4 and 087b0c4.

⛔ Files ignored due to path filters (1)
  • baml_language/Cargo.lock is excluded by !**/*.lock
📒 Files selected for processing (8)
  • baml_language/crates/baml/Cargo.toml
  • baml_language/crates/baml/src/main.rs
  • baml_language/crates/baml/tests/freshness_e2e.rs
  • baml_language/crates/baml_cli/src/agent_command.rs
  • baml_language/crates/baml_cli/tests/agent_install_e2e.rs
  • baml_language/crates/baml_release/Cargo.toml
  • baml_language/crates/baml_release/src/lib.rs
  • baml_language/crates/baml_release/src/skills.rs

Comment thread baml_language/crates/baml/src/main.rs Resolved
Comment thread baml_language/crates/baml/src/main.rs Resolved
ATX24 and others added 2 commits July 10, 2026 13:34
…se pipeline

agent install now pulls the skill repo head directly from GitHub, so the
versioned baml-agent-skills-{version}.tar.gz release asset has no
consumers. Remove the build-agent-skills job, the packaging script, and
the BAML_AGENT_SKILLS_RELEASE_VERSION escape hatch that pointed at it.

Co-authored-by: Cursor <[email protected]>
- agent install --from now clears recorded provenance instead of leaving
  a stale commit that misreports custom content as current
- write_skills_state treats only a missing state.toml as empty; corrupt
  or unreadable files error instead of being silently replaced
- passive cache refreshes share one 5s wall-clock budget instead of up
  to 5s each
- skill detection requires a baml-* directory containing SKILL.md, so
  leftover empty directories don't suppress the install prompt

Co-authored-by: Cursor <[email protected]>
@vercel
vercel Bot temporarily deployed to Preview – promptfiddle2 July 10, 2026 21:13 Inactive
@vercel
vercel Bot temporarily deployed to Preview – beps July 10, 2026 21:13 Inactive
@vercel
vercel Bot temporarily deployed to Preview – promptfiddle July 10, 2026 21:13 Inactive
@vercel
vercel Bot temporarily deployed to Preview – beps July 10, 2026 21:23 Inactive
@vercel
vercel Bot temporarily deployed to Preview – promptfiddle2 July 10, 2026 21:30 Inactive
@vercel
vercel Bot temporarily deployed to Preview – promptfiddle July 10, 2026 21:44 Inactive
…uto-check

The passive path inlined its own fetch-then-persist sequence; route it
through the same helper the explicit toolchain commands use so there is
exactly one fetch-and-cache path and one compare-and-warn path, with
trigger policy (TTL-gated vs forced) as the only difference.

Co-authored-by: Cursor <[email protected]>
…ad of before it

Warnings from existing caches still print immediately (no network).
When a refresh is due (at most once per TTL window), it now runs on a
background thread while baml-cli executes; the wrapper spawns and waits
instead of exec'ing on that rare path, joins the refresh with whatever
remains of the 5s budget after the command exits, and prints only
warnings the fresh caches newly justify (never duplicating one already
shown). The common no-refresh case keeps the zero-overhead exec path.

Co-authored-by: Cursor <[email protected]>
@vercel
vercel Bot temporarily deployed to Preview – beps July 10, 2026 22:19 Inactive

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🧹 Nitpick comments (1)
baml_language/crates/baml/tests/freshness_e2e.rs (1)

223-244: 📐 Maintainability & Code Quality | 🔵 Trivial | 💤 Low value

Consider adding a termination mechanism to the stub server thread.

The incoming() loop runs indefinitely and the JoinHandle is dropped (detached), so the thread and its TcpListener persist until process exit. For a single test this is harmless, but if more tests reuse this helper, detached listeners and threads can accumulate. An AtomicBool flag or std::sync::mpsc channel to break the loop would allow clean shutdown.

This is a test-only concern and can be deferred.

♻️ Optional: add a shutdown flag to the stub server
 fn spawn_stub_commits_server(sha: &str) -> String {
     let listener = TcpListener::bind("127.0.0.1:0").unwrap();
     let base = format!("http://{}", listener.local_addr().unwrap());
     let body = format!(r#"{{"sha":"{sha}"}}"#);
+    let (tx, rx) = std::sync::mpsc::channel::<()>();
     std::thread::spawn(move || {
-        for stream in listener.incoming() {
+        for stream in listener.incoming() {
+            if rx.try_recv().is_ok() { break; }
             let Ok(mut stream) = stream else { continue };
             let mut buf = [0u8; 4096];
             let _ = stream.read(&mut buf);
             let _ = stream.write_all(
                 format!(
                     "HTTP/1.1 200 OK\r\ncontent-type: application/json\r\ncontent-length: {}\r\nconnection: close\r\n\r\n{body}",
                     body.len()
                 )
                 .as_bytes(),
             );
         }
     });
+    // Return (base_url, shutdown_sender) so callers can stop the server.
     base
 }
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@baml_language/crates/baml/tests/freshness_e2e.rs` around lines 223 - 244,
Make spawn_stub_commits_server return a shutdown handle alongside the base URL,
and add an AtomicBool or mpsc channel checked by the listener loop so it can
exit cleanly. Ensure the returned handle signals shutdown and joins the spawned
thread, while preserving the existing request/response behavior.
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Nitpick comments:
In `@baml_language/crates/baml/tests/freshness_e2e.rs`:
- Around line 223-244: Make spawn_stub_commits_server return a shutdown handle
alongside the base URL, and add an AtomicBool or mpsc channel checked by the
listener loop so it can exit cleanly. Ensure the returned handle signals
shutdown and joins the spawned thread, while preserving the existing
request/response behavior.

ℹ️ Review info
⚙️ Run configuration

Configuration used: Repository UI

Review profile: CHILL

Plan: Pro

Run ID: 3a40976d-305c-4f53-b27f-90c003be91a0

📥 Commits

Reviewing files that changed from the base of the PR and between 3a1f825 and 9cd66d8.

📒 Files selected for processing (2)
  • baml_language/crates/baml/src/main.rs
  • baml_language/crates/baml/tests/freshness_e2e.rs
🚧 Files skipped from review as they are similar to previous changes (1)
  • baml_language/crates/baml/src/main.rs

@vercel
vercel Bot temporarily deployed to Preview – promptfiddle2 July 10, 2026 22:26 Inactive
@vercel
vercel Bot temporarily deployed to Preview – promptfiddle July 10, 2026 22:39 Inactive
@ATX24
ATX24 added this pull request to the merge queue Jul 10, 2026
@linear

linear Bot commented Jul 10, 2026 •

Copy link
Copy Markdown

B-820

B-819

Merged via the queue into canary with commit 838efe7 Jul 10, 2026
52 checks passed
@ATX24
ATX24 deleted the dhilan/update-mechanism branch July 10, 2026 23:09
meefs pushed a commit to meefs/baml that referenced this pull request Jul 13, 2026
…lls, and baml-old_skills archive (BoundaryML#4001)

## Summary

Moves the agent-skill freshness system wholly into the toolchain binary
and rounds out the install flow: the "install/upgrade your skill"
warning now ships with every nightly (no wrapper release needed), fires
only on the authoring commands, and `baml agent install` archives
whatever it replaces.

  ### New features

- **Toolchain-owned skill warning** (`skill_check` in `baml_cli`):
before `init`, `run`, `generate`, and `pack` — and only those — the CLI
  checks the project for installed `baml-*` skills and prints one of:
- `warning: No baml skill is installed, set it up with baml agent
install.` (no skills found between the cwd and `$HOME`)
- `warning: Your baml skill is outdated, use baml agent install to
upgrade it.` (installed provenance is behind the skill repo's latest
  commit)

The check never blocks on the network: warnings are decided from local
caches, and a background refresh of the latest-commit cache runs at
most once per 24h (throttled by a marker even when offline, disabled via
`[update] auto_check = false` in `~/.baml/config.toml`). All other
commands — `check`, `describe`, `fmt`, `lsp`, `agent`, etc. — never nag.

- **Replaced skills are archived, not deleted**: when `baml agent
install` overwrites an existing skill, the previous version moves to
`baml-old_skills/<name>/` inside the same skills directory (one slot per
skill — each install keeps the immediately-previous copy). The archive
doubles as the failure-recovery source. Archived copies nest one level
deeper than the `skills/<name>/SKILL.md` layout, so agent harnesses
don't
discover them (verified against a live Claude Code session), the
missing-skill detection ignores them, and `--from <dir>` re-ingestion
filters
  them out.

- **Wrapper cleanup**: all skill-warning machinery is removed from the
`baml` wrapper (pass-through warning, post-`toolchain use/update` nudge,
skill half of the lazy refresh, skill section of `toolchain status`).
None of it had ever shipped — it was added in BoundaryML#3970 without a wrapper
version bump — so published wrapper behavior is unchanged and the
wrapper stays at 0.2.0. The shared logic (warning decision,
project-skills
walk, TTL/marker throttle, auto-check config gate) now lives in
`baml_release::skills`.

  ### Expected behavior (first-run journey)

  Starting from an empty directory:

  ```console
  $ baml init
warning: No baml skill is installed, set it up with baml agent install.
      Creating baml.toml (project)
      Creating baml_src/main.baml

  $ baml agent install
  Installed BAML agent skills in <project>

  Claude Code:
    .claude/skills/baml-*/SKILL.md

  Codex / OpenCode:
    .agents/skills/baml-*/SKILL.md
  ```

- The install downloads the skill repo's main-branch tarball from
`codeload.github.com` — never the GitHub REST API (no credentials, no
unauthenticated rate limit) — resolves the project root from the cwd
(`baml.toml`/`baml_src` owner, bounded by the git repo / `$HOME`), and
records the tarball's source commit as provenance in
`~/.baml/state.toml`.
- If a skill was already installed, the old version is kept at
`.claude/skills/baml-old_skills/baml-core/` (and the `.agents` twin)
while the
  new one replaces `baml-core/`.
- Subsequent `run`/`generate`/`pack`/`init` are silent while the
installed commit matches the repo head; once the skill repo advances
(checked
in the background ≤ once/day), they warn `Your baml skill is outdated…`
until the next `baml agent install`.
- Custom-source installs (`--from <url|tarball|dir>`) record no
provenance, so they keep nudging toward an official install by design.

  ### Tests

- New e2e suites: `skill_warning_e2e.rs` (11 tests: whitelist on/off,
missing vs outdated vs current, background refresh persistence, offline
throttling, auto-check opt-out, archive-not-installed) and the first-run
journey in `agent_install_e2e.rs` (init warns → plain install from a
  codeload stub that 404s any API path → next command quiet).
- Unit tests for the archive rotation (single slot keeps only the
previous version) and the shared warning/throttle helpers in
`baml_release`.
- `exit_code_e2e.rs` now isolates `BAML_HOME` per test so CLI tests
never read the developer's real `~/.baml` or touch the network.

<!-- This is an auto-generated comment: release notes by coderabbit.ai
-->
## Summary by CodeRabbit

- **New Features**
- Added passive, cache-driven agent-skill install/upgrade warnings for
select authoring commands, with TTL-throttled background refresh of the
cached “latest skill commit”.
- Updated agent skill installs to keep replaced versions in a single
`baml-old_skills/` archive slot (per skill name) with rollback on
failure.
- **Bug Fixes**
- Wrapper freshness scope narrowed to channel-manifest only; wrapper no
longer computes or prints agent-skill freshness warnings.
- **Documentation**
- Clarified `update.auto_check` to describe wrapper manifest refresh
only.
- **Tests**
- Revised and added e2e coverage for wrapper toolchain warnings, agent
install/rollback, and passive skill warning behavior.
<!-- end of auto-generated comment: release notes by coderabbit.ai -->

---------

Co-authored-by: Cursor <[email protected]>
Co-authored-by: Claude Fable 5 <[email protected]>

This branch was previously deployed

3 inactive deployments
Preview – promptfiddle — 9cd66d8e Deployed Jul 10, 2026 by vercel[bot]
Preview – promptfiddle2 — 9cd66d8e Deployed Jul 10, 2026 by vercel[bot]
Preview – beps — 9cd66d8e Deployed Jul 10, 2026 by vercel[bot]
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant